/**    
 * 文件名：wechatBroAccessTokenSerivce.java</br>
 *    
 * 版本信息：v1.0</br>
 * 日期：2017年7月3日</br>
 * © 2005-2017 雷技信息科技（上海）有限公司版权所有</br>
 *
 */
package com.logic.landseaserver.common.token.impl;

import java.util.HashMap;
import java.util.Map;

import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.boot.bind.RelaxedPropertyResolver;
import org.springframework.context.EnvironmentAware;
import org.springframework.core.env.Environment;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import com.logic.landseaserver.common.LandseaErrorMessageEnum;
import com.logic.landseaserver.common.enums.WeChatBroMsgEnum;
import com.logic.landseaserver.common.exception.LandseaException;
import com.logic.landseaserver.common.token.AbstractAccessTokenManage;
import com.logic.landseaserver.common.util.HttpRequestClient;
import com.logic.landseaserver.domain.SystemAccessToken;

import net.sf.json.JSONObject;

/**
 *
 * 项目名称：system-server</br>
 * 类名称：WechatBroAccessTokenSerivce</br>
 * 类描述：</br>
 * 创建人：tony</br>
 * 创建时间：2017年7月17日 下午3:50:08</br>
 * @version 1.0
 *
 */
@Service("wechatBroAccessTokenSerivce")
public class WechatBroAccessTokenSerivce extends AbstractAccessTokenManage implements EnvironmentAware 
{
    private static final Logger LOG = LoggerFactory.getLogger(WechatBroAccessTokenSerivce.class);
    private static String accessTokenUrl = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET";
    private static String appid;
    private static String secret;
    private static String templateId;
    private static String turnUrl;
    private static String tradeTemplateId;
    private static String tradeTurnUrl;

    
    private static final String ENV_WECHATBRO = "logic.wechatBro.";
    private static final String APPID = "appid";
    private static final String SECRET = "secret";
    private static final String TEMPLATEID = "templateId";
    private static final String TURNURL = "turnUrl";
    private static final String TRADETEMID = "tradeTemplateId";
    private static final String TRADETURNURL = "tradeTurnUrl";

    private static RelaxedPropertyResolver weChatBropropertyResolver;
    
    private static WechatBroAccessTokenSerivce instance = new WechatBroAccessTokenSerivce();
    
	public static WechatBroAccessTokenSerivce getInstance() {
		return instance;
	}
	
    public String getAppid() {
    	readProperties();
		return appid;
	}

	public String getSecret() {
		readProperties();
		return secret;
	}
	
	public String getTemplateId() {
	    readProperties();
	    return templateId;
	}

	public String getTurnUrl() {
	    readProperties();
	    return turnUrl;
	}

    public String getTradeTemplateId() {
        readProperties();
        return tradeTemplateId;
    }

    public String getTradeTurnUrl() {
        readProperties();
        return tradeTurnUrl;
    }

    @Override
	@Transactional(propagation = Propagation.REQUIRES_NEW, rollbackFor = {LandseaException.class,Exception.class})
    protected SystemAccessToken getDestAccessToken(String tokenId, Object extendObject)
        throws LandseaException
    {
        SystemAccessToken systemAccessToken = new SystemAccessToken();
        systemAccessToken.setDescription("微信公众号access_token");
        systemAccessToken.setTokenId(tokenId);
        try
        {
            readProperties();
        	String url = accessTokenUrl.replace("APPID", appid).replace("APPSECRET", secret);
            LOG.info("WechatBroAccessTokenSerivce|SSLGetRequest URL|" + url);
            
            Map<String, String> headMap = new HashMap<String, String>();
    		headMap.put("Access-Control-Allow-Origin", "*");
    		headMap.put("Access-Control-Allow-Methods", "POST, GET, OPTIONS, DELETE, PUT");
    		headMap.put("Access-Control-Max-Age", "3600");
    		headMap.put("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept, Authorization");
    		headMap.put("Access-Control-Expose-Headers",
    				"MSG, STATUS, COUNT, TOTAL_COUNT, USER_ID, USER_NAME, ORG_ID, size, context, token");
    		String result = HttpRequestClient.getRequest(url,headMap);
            
            LOG.info("WechatBroAccessTokenSerivce|SSLGetRequest response|" + result);
            
            JSONObject tokenjson = JSONObject.fromObject(result);
            
            String accessToken = null;
            
            if (tokenjson.containsKey("access_token"))//正常返回
            {
                accessToken = tokenjson.getString("access_token");
                Long expireLong = tokenjson.getLong("expires_in");
                systemAccessToken.setTokenValue(accessToken);
                // 提前10分钟刷新access_token
                Long expireTime = System.currentTimeMillis() + expireLong*1000;
                systemAccessToken.setExpiretime(expireTime - 600*1000);
            }else
            {
                String errormsg = WeChatBroMsgEnum.valueOf("_" + tokenjson.getString("errcode")).getCode();
                LOG.error("getDestAccessToken|SSLGetResponse Error|" + errormsg);
                throw LandseaException
                    .createException(LandseaErrorMessageEnum.WECHATBRO_GET_ACCESSTOKEN_RESPONSE_ERROR);
            }
            return systemAccessToken;
        }
        catch (LandseaException e)
        {
            throw e;
        }
        catch (Exception e)
        {
            LOG.error("WechatBroAccessTokenSerivce|get wechatBro AccessToken error.", e);
            throw LandseaException.createException(LandseaErrorMessageEnum.WECHAT_BRO_ACCESSTOKEN_ERROR);
        }
    }
    

    @Override
    protected String getTokenId(Object param)
    {
        return "WECHAT_BRO_ACCESSTOKEN";
    }
    

    public String getAccessToken()
        throws LandseaException
    {
        SystemAccessToken systemAccessToken = getAccessToken(getTokenId(null), null);
        return systemAccessToken.getTokenValue();
    }
    
    // 读取配置文件
 	public void readProperties() {
 		try {
 			if(StringUtils.isEmpty(appid) || StringUtils.isEmpty(secret) || StringUtils.isEmpty(templateId)
 			   || StringUtils.isEmpty(turnUrl) ||  StringUtils.isEmpty(tradeTemplateId)
                    || StringUtils.isEmpty(tradeTurnUrl)){
 				appid = weChatBropropertyResolver.getProperty(APPID, String.class);
 	 			secret = weChatBropropertyResolver.getProperty(SECRET, String.class);
 	 			templateId = weChatBropropertyResolver.getProperty(TEMPLATEID, String.class);
 	 			turnUrl = weChatBropropertyResolver.getProperty(TURNURL, String.class);
                tradeTemplateId = weChatBropropertyResolver.getProperty(TRADETEMID,String.class);
                tradeTurnUrl = weChatBropropertyResolver.getProperty(TRADETURNURL,String.class);
 			}
 		} catch (Exception e) {
 		   LOG.error("readProperties error.", e);
 		}
 	}
    
	@Override
	public void setEnvironment(Environment environment) {
		weChatBropropertyResolver = new RelaxedPropertyResolver(environment, ENV_WECHATBRO);
	}
}
